<template>
  <div class="dash-monitor">
    <Row class="stat" :gutter="15">
      <Col flex="200px">
      <Card :dis-hover="true">
        <Circle :size="200" :trail-width="4" :stroke-width="5" :percent="parseFloat(allsuccrate)" stroke-linecap="square" stroke-color="#43a3fb">
          <div class="circle-custom">
            <h1>{{allsucc}}</h1>
            <p>{{$t('page.dash.monitor.allsucc')}}</p>
            <span>{{$t('page.dash.monitor.allsuccrate')}}<i>{{allsuccrate}}</i>%</span>
          </div>
        </Circle>
      </Card>
      <Card class="mt-15" :dis-hover="true">
        <Circle :size="200" :trail-width="4" :stroke-width="5" :percent="parseFloat(onlinerate)" stroke-linecap="square" stroke-color="#43a3fb">
          <div class="circle-custom">
            <h1>{{dash.onlines}}</h1>
            <p>{{$t('page.dash.monitor.onlines')}}</p>
            <span>
              {{$t('page.dash.monitor.nodes')}}<i>{{dash.nodes}}</i>
            </span>
          </div>
        </Circle>
      </Card>
      <Card :dis-hover="true" class="mt-15">
        <Circle :size="200" :trail-width="4" :stroke-width="5" :percent="100" stroke-linecap="square" stroke-color="#43a3fb">
          <div class="circle-custom">
            <h1>{{dash.apps}}</h1>
            <p>{{$t('page.dash.monitor.apps')}}</p>
          </div>
        </Circle>
      </Card>
      </Col>
      <Col flex="800px">
      <Card :dis-hover="true">
        <div ref="container"></div>
      </Card>
      </Col>
      <Col flex="auto">
      <Row>
        <Col span="18">
        <ButtonGroup>
          <Button :type="typebutton(0)" @click="changeListType(0)">{{$t('page.dash.monitor.tb.maxqps')}}</Button>
          <Button :type="typebutton(1)" @click="changeListType(1)">{{$t('page.dash.monitor.tb.count')}}</Button>
          <Button :type="typebutton(2)" @click="changeListType(2)">{{$t('page.dash.monitor.tb.errors')}}</Button>
          <Button :type="typebutton(3)" @click="changeListType(3)">{{$t('page.dash.monitor.tb.rt')}}</Button>
        </ButtonGroup>
        </Col>
        <Col span="6" class="right">
        <Switch v-model="listtotal" size="small" class="mr-5" />
        </Col>
      </Row>
      <List border size="small" class="mt-15">
        <CellGroup>
          <Cell v-for="(stat,i) in liststats" :key="i" :title="listTitle(stat)">
            <template slot="extra">
              {{listShow(stat)}}
            </template>
          </Cell>
        </CellGroup>
      </List>
      </Col>
    </Row>
  </div>
</template>

<script>
  import { Line } from '@antv/g2plot'
  export default {
    data() {
      return {
        dash: {
          apps: 0,
          nodes: 0,
          onlines: 0,
          count: 0,
          errors: 0,
        },
        stats: [],
        liner: null,
        listtotal: false,
        listtype: 0,
        liststats: []
      }
    },
    computed: {
      allsucc() {
        return this.dash.count - this.dash.errors
      },
      allsuccrate() {
        if (this.dash.count === 0) return 0
        let allsucc = this.allsucc
        if (allsucc === 0) return 0
        if (allsucc === this.dash.count) return 100
        let allsuccrate = (allsucc * 100 / this.dash.count)
        return allsuccrate.toFixed(4)
      },
      onlinerate() {
        if (this.dash.nodes === 0) return 0
        if (this.dash.onlines === 0) return 0
        return (this.dash.onlines * 100 / this.dash.nodes).toFixed(0)
      },
    },
    watch: {
      listtotal() {
        this.changeListType(-1)
      }
    },
    created() {
      this.loadDash()
    },
    mounted() {
      this.renderLiner()
      this.$nextTick(() => {
        this.loadDashLine()
      })
    },
    methods: {
      typebutton(type) {
        return this.listtype === type ? 'primary' : 'default'
      },
      loadDash() {
        this.$md.dispatch('home_dash').then(data => {
          if (data.retCode === 1) {
            this.dash.apps = data.apps
            this.dash.count = data.count
            this.dash.errors = data.errors
            this.dash.nodes = data.nodes
            this.dash.onlines = data.onlines
          }
        })
      },
      loadDashLine() {
        this.$md.dispatch('home_dashstat').then(data => {
          if (data.retCode === 1) {
            let stats = data.data || []
            let stat
            for (let i in stats) {
              stat = stats[i]
              stat.daydatefmt = new Date(stat.daydate).dateFormat()
            }
            this.stats = stats
            //
            let lineData = []
            let lineDataMap = {}
            let statData
            for (let i in stats) {
              stat = stats[i]
              statData = lineDataMap[stat.daydatefmt]
              if (statData) {
                statData[0].value = Math.max(statData[0].value, stat.maxqps)
                statData[1].value += stat.count
                statData[2].value += stat.errors
                statData[3].value = Math.max(statData[3].value, stat.maxTime)
              } else {
                lineDataMap[stat.daydatefmt] = [
                  {
                    date: stat.daydatefmt,
                    value: stat.maxqps,
                    category: 'MaxQPS'
                  },
                  {
                    date: stat.daydatefmt,
                    value: stat.count,
                    category: 'Request'
                  },
                  {
                    date: stat.daydatefmt,
                    value: stat.errors,
                    category: 'Request Error'
                  },
                  {
                    date: stat.daydatefmt,
                    value: stat.maxTime,
                    category: 'Max RT'
                  },
                ]
              }
            }

            for (let d in lineDataMap) {
              lineData.push.apply(lineData, lineDataMap[d])
            }
            //
            lineData.sort((s1, s2) => {
              return s1.date.localeCompare(s2.date)
            })

            this.liner.update({ data: lineData })
            //
            this.changeListType(-1)
          }
        })
      },
      renderLiner() {
        this.liner = new Line(this.$refs.container, {
          data: [],
          padding: 'auto',
          xField: 'date',
          yField: 'value',
          seriesField: 'category',
        })
        this.liner.render()
      },
      changeListType(type) {
        if (type === -1) type = this.listtype
        let rtype = this.listtype = type
        let liststats = []
        let stats = this.stats
        //
        if (this.listtotal) {
          // 合并不同日期的appname的数据
          let statDataMap = {}
          let statData
          let stat
          for (let i in stats) {
            stat = stats[i]
            statData = statDataMap[stat.appname]
            if (statData) {
              statData.maxqps = Math.max(statData.maxqps, stat.maxqps)
              statData.count += stat.count
              statData.errors += stat.errors
              statData.maxTime = Math.max(statData.maxTime, stat.maxTime)
            } else {
              statDataMap[stat.appname] = {
                appname: stat.appname,
                maxqps: stat.maxqps,
                count: stat.count,
                errors: stat.errors,
                maxTime: stat.maxTime,
              }
            }
          }
          //
          for (let d in statDataMap) {
            liststats.push(statDataMap[d])
          }
        } else {
          liststats = stats
        }
        //
        liststats.sort((s1, s2) => {
          switch (rtype) {
            case 1:
              return s2.count - s1.count
            case 2:
              return s2.errors - s1.errors
            case 3:
              return s2.maxTime - s1.maxTime
            case 0:
            default:
              return s2.maxqps - s1.maxqps
          }
        })

        this.liststats = liststats.slice(0, 20)
      },
      listTitle(stat) {
        if (this.listtotal) {
          return stat.appname
        } else {
          return '[' + stat.daydatefmt + ']' + stat.appname
        }
      },
      listShow(stat) {
        switch (this.listtype) {
          case 1:
            return stat.count + ''
          case 2:
            return stat.errors + ''
          case 3:
            return stat.maxTime + 'ms'
          case 0:
          default:
            return stat.maxqps + ''
        }
      },
    }
  };
</script>

<style lang="less" scoped>
  .dash-monitor {
    height: calc(100% - 45px);
    background-color: #fff;
    padding: 15px;

    .stat {
      .header {
        color: #808695;
      }
      .data {
        font-size: 32px;
        color: #2d8cf0;
      }
      .circle-custom {
        font-size: 12px;
        & h1 {
          color: #2d8cf0;
          font-size: 32px;
          font-weight: 600;
        }
        & p {
          color: #657180;
          font-size: 14px;
          margin: 10px 0 15px;
        }
        & span {
          display: block;
          padding-top: 15px;
          color: #657180;
          font-size: 14px;
          &:before {
            content: '';
            display: block;
            width: 50px;
            height: 1px;
            margin: 0 auto;
            background: #e0e3e6;
            position: relative;
            top: -15px;
          }
        }
        & span i {
          color: #3f414d;
          font-style: normal;
          font-size: 16px;
          margin: 0 2px;
        }
      }
    }
  }
</style>
